package net.zjitc.security.auth;

import net.zjitc.entity.Permission;
import net.zjitc.service.IPermissionService;
import org.apache.dubbo.config.annotation.Reference;
import org.springframework.security.access.ConfigAttribute;
import org.springframework.security.web.FilterInvocation;
import org.springframework.security.web.access.intercept.FilterInvocationSecurityMetadataSource;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import org.springframework.stereotype.Component;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

@Component
public class MySecurityMetadataSource implements FilterInvocationSecurityMetadataSource {
    @Reference
    private IPermissionService permissionService;

    private List<Permission> permissionList;

    /**
     *
     * @param object
     * @return
     * @throws IllegalArgumentException
     */
    @Override
    public Collection<ConfigAttribute> getAttributes(Object object) throws IllegalArgumentException {

        //加载数据库的权限信息
        if (permissionList == null){ this.loadResource();}
        HttpServletRequest request = ((FilterInvocation) object).getRequest();
        //加载访问url时所需要的权限
        //权限集合的存储
        List<ConfigAttribute> allConfigAttribute = new ArrayList<>();
        AntPathRequestMatcher matcher;
        //权限集合的查询
        boolean flag = false;
        for (Permission permission : permissionList) {
            //使用AntPathRequestMatcher比较可让url支持ant风格,例如/user/*/a
            //*匹配一个或多个字符，**匹配任意字符或目录
            matcher = new AntPathRequestMatcher("/"+permission.getPath());
            if (matcher.matches(request)) {
                ConfigAttribute configAttribute = new MyConfigAttribute(new MyGrantedAuthority(String.valueOf(permission.getId())));
                allConfigAttribute.add(configAttribute);
                //这里是获取到一个权限就返回,根据校验规则也可获取多个然后返回
                //return allConfigAttribute;
                flag = true;
            }
        }

        if (flag){
            return allConfigAttribute;
        }

        //未匹配到，说明无需权限验证
        // 如果没有匹配，则默认全部可以访问
        return null;
    }

    /**
     * 加载数据库的权限信息
     */
    private void loadResource() {
        this.permissionList = permissionService.selectList();
    }

    @Override
    public Collection<ConfigAttribute> getAllConfigAttributes() {
        return null;
    }

    @Override
    public boolean supports(Class<?> clazz) {
        return false;
    }

}
